
const Views=require('../models/Views.js')
/*
获取HTTP请求参数
* query string  可选 ?q=keyword  ctx.query
* router params 必选 /users/:id  ctx.params
* body {name:'王家辉'}           ctx.request.body
*
响应头信息
* status 200/400
* body {name:'王家辉'}
* header allow content-type
*
* */
class ViewCtl {
    async find(ctx) {
        // 每页条数
        const perPage = parseInt(ctx.query.perPage) || 10
        // 当前页
        const page = parseInt(ctx.query.page) || 1
        // 跳过条数
        const skip = (page - 1) * perPage
        // 分页 模糊搜索
        const q = new RegExp(ctx.query.q)
        const list = await Views.find({name: q}).limit(perPage).skip(skip)
        // 总页数
        const total = await Views.find({name: q}).countDocuments()
        // 向上取整 一共有多少页
        const totalPage = Math.ceil(total / perPage)
        ctx.body = {
            list,
            page,
            perPage,
            total,
            totalPage,
        }
    }

    async findById(ctx) {
        // http://localhost:3000/users/5e48e26bfb874d2f6ca2ace7?fields=introduction
        // ?fields后面写上指定的参数，即可查询并返回指定的字段
        const {fields = ''} = ctx.query
        // fields可能是一个空字符串，需要使用filter过滤一下
        // 这following;locations;business三个字段即可可以正常查询
        const selectFields = fields.split(';').filter(f => f).map(f => ' +' + f).join('')
        console.log(selectFields);
        // populateStr进行深度查询，获取employments;educations中的对象
        const populateStr = fields.split(';').filter(f => f).map(f => {
            if (f === 'employments') {
                return 'employments.company employments.job'
            }
            if (f === 'educations') {
                return 'educations.school educations.major'
            }
            return f
        }).join(' ')
        console.log(populateStr);
        // 显示selectFields、populateStr中的字段，但里面只有id，根据id查询用户字段里的具体信息，需要集合联合查询
        var user = await Users.findById(ctx.params.id).select(selectFields).populate(populateStr)
        if (!user) ctx.throw(404, '此用户不存在')
        ctx.body = user
    }

    async create(ctx) {
        // 验证 用户名、密码是必须的，所以required为true
        ctx.verifyParams({
            name: {type: 'string', required: true},
            password: {type: 'string', required: true},
        })
        const {name} = ctx.request.body
        const repeatedUser = await Views.findOne({name})
        if (repeatedUser)  {
            repeatedUser.count += 1
            repeatedUser.save()
            ctx.throw(409, '此用户已被占用')
        }
        var user = await new Views(ctx.request.body)
        user.count = 1
        user.save()
        ctx.body = user

        // var user = Users.create(ctx.request.body)
        // ctx.body = user
    }

    // 此用户已存在中间件(暂不需要)
    async checkUser(ctx, next) {
        const {name} = ctx.request.body
        const repeatedUser = await Users.findOne({name})
        if (repeatedUser) {
            ctx.throw(409, '此用户已被占用')
        } else {
            next()
        }
    }

    // 授权处理中间件
    async checkOwner(ctx, next) {
        // 已经登录就有ctx.state.user字段
        if (ctx.params.id !== ctx.state.user._id) {
            ctx.throw(403, '没有权限')
        } else {
            await next()
        }
    }

    async update(ctx) {
        ctx.verifyParams({
            name: {type: 'string', required: false},
            password: {type: 'string', required: false},
            avatar_url: {type: 'string', required: false},
            gender: {type: 'string', required: false},
            headline: {type: 'string', required: false},
            locations: {type: 'array', itemType: 'string', required: false},
            business: {type: 'string', required: false},
            employments: {type: 'array', itemType: 'object', required: false},
            educations: {type: 'array', itemType: 'object', required: false},
        })
        var user = await Users.findByIdAndUpdate(ctx.params.id, ctx.request.body)
        if (!user) ctx.throw(404, '此用户不存在')
        ctx.body = user
        // 注：返回的是更新前的user，mongoose的findByIdAndUpdate语法问题，待优化
        // {
        //     "avatar_url":"http://localhost:3000/uploads/upload_bc234b04a43c94b38bee7142c5076ad2.png",
        //     "gender":"male",
        //     "headline":"天地滂沱如何渡？蓑衣褪尽任浊流。",
        //     "localtions":["5e58898d42a9f10340e2bdc4"],
        //     "business":"5e58d169bc818009cc427bac",
        //     "employments":[{"company":"5e58898d42a9f10340e2bdc4","job":"5e58897642a9f10340e2bdc1"}],
        //     "educations":[{"school":"5e58898a42a9f10340e2bdc3","major":"5e58893a42a9f10340e2bdc0"}]
        // }
        // 话题引用了用户，所以更新的时候需要传话题的id，即可关联
    }

    async remove(ctx) {
        var user = await Views.findByIdAndRemove(ctx.params.id)
        if (!user) ctx.throw(404, '此用户不存在')
        ctx.body = {message: '删除成功'}
    }

    async login(ctx) {
        ctx.verifyParams({
            // 验证 用户名、密码是必须的，所以required为true
            name: {type: 'string', required: true},
            password: {type: 'string', required: true},
        })
        var user = await Users.findOne(ctx.request.body)
        if (!user) {
            ctx.throw(401, '用户名或密码错误')
        }
        var {_id, name} = user
        const token = await jsonwebtoken.sign({_id, name}, secret, {expiresIn: 1000 * 60 * 60 * 24})
        ctx.body = {
            token
        }

    }
    async userInfo(ctx){
        const token = ctx.header.authorization
        ctx.body = {
            token,
            data: ctx.state
        }
    }

    // 获取用户的关注列表
    async listFollowing(ctx) {
        // var user= await Users.findById(ctx.params.id).select('+following')
        // {
        //     "avatar_url": null,
        //     "gender": "male",
        //     "headline": null,
        //     "following": [
        //         "61baf3d4f88fe51b3444f762",
        //         "61baf4acb8ee320d68f3abe7"
        //     ],
        //     "_id": "61baecf6fed1b55bec39a146",
        //     "name": "独孤求败",
        //     "password": "123456",
        //     "createdAt": "2021-12-16T07:38:30.736Z",
        //     "updatedAt": "2021-12-20T04:25:53.954Z"
        // }
        // 显示following字段，但following字段里面只有id；根据id查询用户具体信息，需要集合联合查询
        var user = await Users.findById(ctx.params.id).populate('following')
        if (!user) {
            ctx.throw(404)
        }
        ctx.body = user
    }

    // 校验用户是否存在中间件
    // 注：没有实现，id不存在，报500
    //已实现，id不存在，即显示提示
    async checkUserExist(ctx, next) {
        const user = await Users.findById(ctx.params.id)
        if (!user) {
            ctx.throw(404, '用户不存在')
        } else {
            await next()
        }
    }

    // 关注
    async follow(ctx) {
        // 已经登录就有ctx.state.user字段
        // var me=await Users.findById(ctx.state.user._id).select('+following')
        // {
        //     "avatar_url": null,
        //     "gender": "male",
        //     "headline": null,
        //     "following": ["61baf4acb8ee320d68f3abe7"],
        //     "_id": "61c049b97b5cdf260822b6ff",
        //     "password": "123456",
        //     "name": "岳灵珊",
        //     "createdAt": "2021-12-20T09:15:37.165Z",
        //     "updatedAt": "2021-12-20T09:37:37.601Z"
        // }
        // 数据转换，将mongodb文档对象转换为js对象，没有关注则push进来
        var me = await Users.findById(ctx.state.user._id).select('+following')
        if (!me.following.map(id => id.toString()).includes(ctx.params.id)) {
            me.following.unshift(ctx.params.id)
            me.save()
            ctx.status = 204//关注成功
        } else {
            ctx.body = {message: "您已关注", user: ctx.state}
            // {
            //     "message": "您已关注",
            //     "user": {
            //     "user": {
            //             "_id": "61bff83a50ef6c51ec1392ba",
            //             "name": "任盈盈----",
            //             "iat": 1641795833,
            //             "exp": 1645395833
            //     }
            // }
            // }
            // TODO 修改用户之后，应该重新登录一下，因为ctx.state中保存的还是之前未修改的用户数据，等待解决
        }
    }

    // 取消关注
    async unfollow(ctx) {
        // 已经登录就有ctx.state.user字段
        var me = await Users.findById(ctx.state.user._id).select('+following')
        // 获取要取消关注的人的id在自己列表中following数组的下标
        var index = me.following.map(id => id.toString()).indexOf(ctx.params.id)
        if (index > -1) {
            me.following.splice(index, 1)
            me.save()
            ctx.status = 204//取消关注成功
        } else {
            ctx.body = {message: "该用户不存在"}
        }
    }

    // 获取用户的粉丝列表
    async listFollowers(ctx) {
        // var user=await Users.find().select('+following')
        // {
        //     avatar_url: null,
        //         gender: 'male',
        //     headline: null,
        //     following: [ 61bff83a50ef6c51ec1392ba ],
        //     _id: 61baf4acb8ee320d68f3abe7,
        //     name: '令狐冲',
        //     password: '123456',
        //     createdAt: 2021-12-16T08:11:24.018Z,
        //     updatedAt: 2021-12-20T10:13:05.587Z
        // },
        // {
        //     avatar_url: null,
        //         headline: null,
        //     following: [ 61baf4acb8ee320d68f3abe7, 61bff83a50ef6c51ec1392ba ],
        //     _id: 61c049b97b5cdf260822b6ff,
        //     password: '123456',
        //     name: '岳灵珊',
        //     createdAt: 2021-12-20T09:15:37.165Z,
        //     updatedAt: 2021-12-20T09:46:20.579Z
        // }
        // ...
        // following数组中必须包含ctx.params.id，即已关注
        var user = await Users.find({following: ctx.params.id})
        ctx.body = user
    }

    // 获取用户的提问列表
    // 提问者-问题 一对多关系
    async listQuestions(ctx) {
        const questions = await Questions.find({questioner: ctx.params.id})
        ctx.body = questions
    }

    // 用户点赞列表
    async listLikingAnswers(ctx) {
        const user = await Users.findById(ctx.params.id).select('+likingAnswers').populate('likingAnswers')
        if (!user) {
            ctx.throw(404, '用户不存在')
        }
        ctx.body = user.likingAnswers
    }

    // 点赞
    async likeAnswer(ctx, next) {
        const me = await Users.findById(ctx.state.user._id).select('+likingAnswers')
        if (!me.likingAnswers.map(id => id.toString()).includes(ctx.params.id)) {
            me.likingAnswers.push(ctx.params.id)
            me.save()
            // 更新投票数
            await Answers.findByIdAndUpdate(ctx.params.id, {$inc: {voteCount: 1}})
            ctx.status = 204
            await next()
        } else {
            ctx.body = {message: '已点赞'}
        }

    }

    // 取消点赞
    async unlikeAnswer(ctx) {
        var me = await Users.findById(ctx.state.user._id).select('+likingAnswers')
        // 获取要取消关注的人的id在自己列表中following数组的下标
        var index = me.likingAnswers.map(id => id.toString()).indexOf(ctx.params.id)
        if (index > -1) {
            me.likingAnswers.splice(index, 1)
            me.save()
            await Answers.findByIdAndUpdate(ctx.params.id, {$inc: {voteCount: -1}})
            ctx.status = 204
        } else {
            ctx.body = {message: '已取消点赞'}
        }

    }

    // 用户踩列表
    async listDislikingAnswers(ctx) {
        const user = await Users.findById(ctx.params.id).select('+dislikingAnswers').populate('dislikingAnswers')
        if (!user) {
            ctx.throw(404, '用户不存在')
        }
        ctx.body = user.dislikingAnswers

    }

    // 点踩
    async DislikeAnswer(ctx, next) {
        const me = await Users.findById(ctx.state.user._id).select('+dislikingAnswers')
        if (!me.dislikingAnswers.map(id => id.toString()).includes(ctx.params.id)) {
            me.dislikingAnswers.push(ctx.params.id)
            me.save()
            // await Answers.findByIdAndUpdate(ctx.params.id,{$inc:{voteCount:1}})
        }
        ctx.status = 204
        await next()
    }

    // 取消点踩
    async unlDisikeAnswer(ctx) {
        var me = await Users.findById(ctx.state.user._id).select('+dislikingAnswers')
        // 获取要取消关注的人的id在自己列表中following数组的下标
        var index = me.dislikingAnswers.map(id => id.toString()).indexOf(ctx.params.id)
        if (index > -1) {
            me.dislikingAnswers.splice(index, 1)
            me.save()
            ctx.status = 204//取消关注成功
            // await Answers.findByIdAndUpdate(ctx.params.id,{$inc:{voteCount:-1}})
        }
        ctx.status = 204
    }

    // 用户收藏答案列表
    async listCollectAnswers(ctx) {
        const user = await Users.findById(ctx.params.id).select('+collectingAnswers').populate('collectingAnswers')
        if (!user) {
            ctx.throw(404, '用户不存在')
        }
        ctx.body = user.collectingAnswers

    }

    // 收藏
    async collectAnswer(ctx, next) {
        const me = await Users.findById(ctx.state.user._id).select('+collectingAnswers')
        if (!me.collectingAnswers.map(id => id.toString()).includes(ctx.params.id)) {
            me.collectingAnswers.push(ctx.params.id)
            me.save()
            // await Answers.findByIdAndUpdate(ctx.params.id,{$inc:{voteCount:1}})
        }
        ctx.status = 204
        await next()
    }

    // 取消收藏
    async uncollctAnswer(ctx) {
        var me = await Users.findById(ctx.state.user._id).select('+collectingAnswers')
        // 获取要取消关注的人的id在自己列表中following数组的下标
        var index = me.collectingAnswers.map(id => id.toString()).indexOf(ctx.params.id)
        if (index > -1) {
            me.collectingAnswers.splice(index, 1)
            me.save()
            // ctx.status=204//取消关注成功
            // await Answers.findByIdAndUpdate(ctx.params.id,{$inc:{voteCount:-1}})
        }
        ctx.status = 204
    }


}

module.exports = new ViewCtl()
